package models;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import objects.Feature;
import objects.Features;
import objects.FeaturesDatabase;
import objects.Lexicon;

import org.w3c.dom.Attr;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.xml.sax.SAXException;

/* Accessible only through LexiconFeaturesModel */
class LexiconFeatureXMLReader {
	
	private FeaturesDatabase db;
	
	public LexiconFeatureXMLReader() {
		db = null;
	}
	
	public void read(String fileLocation) throws ParserConfigurationException, SAXException, IOException {
		DocumentBuilderFactory docBuilderFactory = DocumentBuilderFactory.newInstance();
		DocumentBuilder docBuilder = docBuilderFactory.newDocumentBuilder();
		Document doc = docBuilder.parse(new File(fileLocation));
		
		db = (FeaturesDatabase) getXML(doc.getDocumentElement());
		
	}
	
	public Object getXML(Node node) {
		
		Object created = null;
		
		if (node.getNodeName().equals("featureslist")) {
			FeaturesDatabase db = new FeaturesDatabase();
			
			db.initializeLexicons();
			
			created = db;
		}
		else if (node.getNodeName().equals("pos")) {
			Lexicon lexicon = new Lexicon();
			
			Attr label = (Attr) node.getAttributes().getNamedItem("label");
			String strLabel = null;
			
			if (label != null) {
				strLabel = new String(label.getValue());
			}
			
			Features features = new Features();
			
			lexicon.setLabel(strLabel);
			lexicon.setFeatures(features);
			
			created = lexicon;
		}
		else if (node.getNodeName().equals("feature")) {
			Feature feature = new Feature();
			feature.setValue(null);
			
			Attr name = (Attr) node.getAttributes().getNamedItem("name");
			Attr editable = (Attr) node.getAttributes().getNamedItem("editable");
			
			String strName = null;
			boolean boolEditable = false;
			
			if (name != null) {
				strName = new String(name.getValue());
			}
			if (editable != null) {
				boolEditable = Boolean.parseBoolean(editable.getValue());
			}
			
			feature.setName(strName);
			feature.setEditable(boolEditable);
			
			created = feature;
		}
		else if (node.getNodeName().equals("value")) {
			String value = node.getTextContent().trim();
			
			created = value;
		}

		if (node.hasChildNodes()) {
			for (int i = 0; i < node.getChildNodes().getLength(); i++) {
				Object returnedType = getXML(node.getChildNodes().item(i));
				if (returnedType != null) {
				}

				if (returnedType != null) {
					if (returnedType.getClass().getName() == "objects.Lexicon") {
						FeaturesDatabase db = (FeaturesDatabase) created;
						Lexicon lexicon = (Lexicon) returnedType;
						
						db.addLexicon(lexicon);
					}
					else if (returnedType.getClass().getName().equals("objects.Feature")) {
						Lexicon lexicon = (Lexicon) created;
						Feature feature = (Feature) returnedType;
						
						lexicon.addFeatureListItem(feature);
					}
					else if (returnedType.getClass().getName().equals("java.lang.String")) {
						Feature feature = (Feature) created;
						String value = (String) returnedType;
						
						feature.addValueListItem(value);
					}
				}
			}
		}
		
		return created;
	}
	
	public ArrayList<Lexicon> getDatabase() {
		return db.getLexicons();
	}
	
}
